////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// Copyright (c) 2017-2018 Qualcomm Technologies, Inc.
// All Rights Reserved.
// Confidential and Proprietary - Qualcomm Technologies, Inc.
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// @file  camxncssensor.cpp
/// @brief CamX NCS Sensor implementation
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

#include "camxdefs.h"
#include "camxincs.h"
#include "camxncsintfqsee.h"
#include "camxncssensordata.h"
#include "camxncssensor.h"
#include "camxncsservice.h"
#include "camxutils.h"

CAMX_NAMESPACE_BEGIN

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetLastNSamples
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
NCSSensorData* NCSSensor::GetLastNSamples(
    UINT numOfSamples)
{
    INCSIntfBase* pNCSIntfObject = m_NCSSensorContext.pNCSIntfObject;
    CAMX_ASSERT_MESSAGE(NULL != pNCSIntfObject, "NULL NCS interface object");
    return static_cast<NCSSensorData*>
        (pNCSIntfObject->GetLastNSamples(numOfSamples, m_NCSSensorContext.connIndex));
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetDataSync
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
NCSSensorData* NCSSensor::GetDataSync(
    UINT64 tStart,
    UINT64 tEnd)
{
    INCSIntfBase*  pNCSIntfObject = NULL;
    NCSSensorType  sensorType     = NCSMaxType;
    NCSSensorData* pNCSDataObj    = NULL;

    pNCSIntfObject = m_NCSSensorContext.pNCSIntfObject;
    sensorType = GetSensorType();
    CAMX_ASSERT_MESSAGE(((sensorType >= 0) && (sensorType < NCSMaxType)),
                        "Invalid sensor type sensorType %d", sensorType);

    CAMX_LOG_VERBOSE(CamxLogGroupNCS, "Getting data sync tStart %llu tEnd %llu", tStart, tEnd);

    if (NULL != pNCSIntfObject)
    {
        pNCSDataObj = static_cast<NCSSensorData*>(pNCSIntfObject->GetDataSync(tStart, tEnd, m_NCSSensorContext.connIndex));
    }
    else
    {
        CAMX_LOG_ERROR(CamxLogGroupNCS, "Invalid interface handle !! Returning null accessor.");
        pNCSDataObj = NULL;
    }

    return pNCSDataObj;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetIntfHandle
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
INCSIntfBase* NCSSensor::GetIntfHandle()
{
    return m_NCSSensorContext.pNCSIntfObject;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetSensorType
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
NCSSensorType NCSSensor::GetSensorType()
{
    return m_NCSSensorContext.config.sensorType;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::FillSensorConfig
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CamxResult NCSSensor::FillSensorConfig(
    NCSSensorConfig* pConfig)
{
    CamxResult result = CamxResultSuccess;
    if (NULL == pConfig)
    {
        result =  CamxResultEFailed;
    }
    else
    {
        *pConfig = m_NCSSensorContext.config;
    }
    return result;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::PutBackDataObj
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CamxResult NCSSensor::PutBackDataObj(
    NCSSensorData* pNCSDataObject)
{
    NCSSensorType  sensorType;
    INCSIntfBase*  pNCSIntfObject  = m_NCSSensorContext.pNCSIntfObject;
    CamxResult     result           = CamxResultEFailed;
    if ((NULL != pNCSIntfObject) && (NULL != pNCSDataObject))
    {
        sensorType = GetSensorType();
        // Unlock the buffer current position if it has locked it.
        pNCSIntfObject->ClearBufferLock(sensorType);
        // Clear the flag that this acessor has lockd the buffer
        pNCSDataObject->ClearHaveBufLocked();

        result = pNCSIntfObject->EnqueueAccessor(static_cast<VOID*>(pNCSDataObject));
    }
    else
    {
        CAMX_LOG_ERROR(CamxLogGroupNCS, "Unable to put back object, NULL intf or acessor object");
    }
    return result;
}


////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::SetConnIndex
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CAMX_VISIBILITY_PUBLIC VOID NCSSensor::SetConnIndex(
    INT connIndex)
{
    m_NCSSensorContext.connIndex = connIndex;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetConnIndex
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CAMX_VISIBILITY_PUBLIC INT NCSSensor::GetConnIndex()
{
    return m_NCSSensorContext.connIndex;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::SetCurrentConfig
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CAMX_VISIBILITY_PUBLIC VOID NCSSensor::SetCurrentConfig(
    NCSSensorConfig* pConfig)
{
    m_NCSSensorContext.currSampleRate = pConfig->samplingRate;
    m_NCSSensorContext.curReportRate  = pConfig->reportRate;
    return;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetSampleRate
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CAMX_VISIBILITY_PUBLIC FLOAT NCSSensor::GetSampleRate()
{
    return  m_NCSSensorContext.currSampleRate;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetReportRate
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CAMX_VISIBILITY_PUBLIC UINT NCSSensor::GetReportRate()
{
    return  m_NCSSensorContext.curReportRate;
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::GetDataAsync
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
CamxResult NCSSensor::GetDataAsync(
    UINT64 tStart,
    UINT64 tEnd,
    VOID* pFence)
{
    INCSIntfBase* pNCSIntfObject = m_NCSSensorContext.pNCSIntfObject;

    CAMX_ASSERT(NULL != pNCSIntfObject);

    return pNCSIntfObject->GetDataAsync(tStart, tEnd, m_NCSSensorContext.connIndex, pFence);
}

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// NCSSensor::NCSSensor
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
NCSSensor::NCSSensor(
    INCSIntfBase*    pNCSIntfObject,
    NCSSensorConfig* pSensorConfig)
{
    m_NCSSensorContext.pNCSIntfObject        = pNCSIntfObject;
    m_NCSSensorContext.config                = *pSensorConfig;

    // Add log to print the sensor config. The actual link is established when after the pipeline is created.
    CAMX_LOG_VERBOSE(CamxLogGroupNCS, "Creating sensor object for config samplerate %f  reportrate %d type %d",
        pSensorConfig->samplingRate, pSensorConfig->reportRate, pSensorConfig->sensorType);
}

CAMX_NAMESPACE_END